package com.yhn.bubblevideo.user.service.impl;


import cn.hutool.core.collection.CollUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.yhn.bubblevideo.common.enums.BaseErrorCode;
import com.yhn.bubblevideo.common.exception.BusinessException;
import com.yhn.bubblevideo.common.exception.ThrowUtils;
import com.yhn.bubblevideo.model.domain.Comment;
import com.yhn.bubblevideo.model.dto.req.comment.CommentAddRequestDTO;
import com.yhn.bubblevideo.model.dto.req.comment.CommentEditRequestDTO;
import com.yhn.bubblevideo.model.dto.req.comment.CommentQueryRequestDTO;
import com.yhn.bubblevideo.model.dto.req.common.DeleteRequest;
import com.yhn.bubblevideo.model.dto.resp.CommentRespDTO;
import com.yhn.bubblevideo.model.dto.resp.UserRespDTO;
import com.yhn.bubblevideo.user.mapper.CommentMapper;
import com.yhn.bubblevideo.user.service.CommentService;
import com.yhn.bubblevideo.user.service.UserService;
import jakarta.annotation.Resource;
import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.stream.Collectors;

import static com.yhn.bubblevideo.common.constant.CommonConstant.MAX_PAGE_SIZE;

/**
 * @author yhnyhn123
 * @description 针对表【comment(用户评论表)】的数据库操作Service实现
 * @createDate 2024-11-21 13:33:34
 */
@Service
public class CommentServiceImpl extends ServiceImpl<CommentMapper, Comment>
        implements CommentService {

    @Resource
    private UserService userService;

    /**
     * 分页查询
     */
    @Override
    public Page<CommentRespDTO> queryPage(CommentQueryRequestDTO requestParam) {
        if (requestParam == null) {
            throw new BusinessException(BaseErrorCode.PARAMS_ERROR);
        }
        long current = requestParam.getCurrent();
        long size = requestParam.getPageSize();
        // 限制爬虫
        ThrowUtils.throwIf(size > MAX_PAGE_SIZE, BaseErrorCode.PARAMS_ERROR);
        Page<Comment> commentPage = this.page(new Page<>(current, size),
                this.getQueryWrapper(requestParam));
        Page<CommentRespDTO> commentRespPage = new Page<>(current, size, commentPage.getTotal());
        List<CommentRespDTO> commentVO = this.getCommentVO(commentPage.getRecords());
        commentRespPage.setRecords(commentVO);
        return commentRespPage;
    }

    @Override
    public LambdaQueryWrapper<Comment> getQueryWrapper(CommentQueryRequestDTO requestParam) {

        if (requestParam == null) {
            return null;
        }

        return new LambdaQueryWrapper<>();
    }

    /**
     * 获取脱敏对象集合
     *
     * @param commentList 查询请求
     * @return 脱敏对象集合
     */
    @Override
    public List<CommentRespDTO> getCommentVO(List<Comment> commentList) {
        if (CollUtil.isEmpty(commentList)) {
            return new ArrayList<>();
        }
        return commentList.stream().map(this::getCommentVO).collect(Collectors.toList());
    }


    /**
     * 将对象转化为脱敏对象
     *
     * @param comment 原对象
     * @return 脱敏对象
     */
    @Override
    public CommentRespDTO getCommentVO(Comment comment) {
        if (comment == null) {
            return null;
        }
        CommentRespDTO commentResp = new CommentRespDTO();
        BeanUtils.copyProperties(comment, commentResp);
        List<Comment> children = null;
        //获取当前评论的所有子评论
        if (comment.getParentId() == null) {
            children = baseMapper.selectList(Wrappers.lambdaQuery(Comment.class)
                    .eq(Comment::getParentId, comment.getId()));
        }
        //将用户ID和回复用户ID转化为用户名和头像
        if (comment.getUserId() != null) {
            UserRespDTO infoById = userService.getInfoById(comment.getUserId());
            commentResp.setUserName(infoById.getNickname());
            commentResp.setUserAvatar(infoById.getUserAvatar());
        }
        if (comment.getReplyUserId() != null) {
            UserRespDTO infoById = userService.getInfoById(comment.getReplyUserId());
            commentResp.setReplyUserName(infoById.getNickname());
            commentResp.setReplyUserAvatar(infoById.getUserAvatar());
        }
        List<CommentRespDTO> childrenResp = null;
        if (children != null) {
            childrenResp = children.stream()
                    .map(this::getCommentVO)
                    .collect(Collectors.toList());
        }
        commentResp.setChildren(childrenResp);
        return commentResp;
    }

    /**
     * 根据ID获取信息
     *
     * @param id id
     * @return 实体信息
     */
    @Override
    public CommentRespDTO getInfoById(Long id) {
        Comment comment = baseMapper.selectById(id);
        if (comment == null) {
            throw new BusinessException(BaseErrorCode.NOT_FOUND_ERROR, "没有对应的信息");
        }
        return getCommentVO(comment);
    }

    /**
     * 保存信息
     *
     * @param requestParam 添加请求
     * @return 新生成的ID
     */
    @Override
    @Transactional
    public Long saveComment(CommentAddRequestDTO requestParam) {
        if (requestParam == null) {
            throw new BusinessException(BaseErrorCode.PARAMS_ERROR);
        }
        LambdaQueryWrapper<Comment> queryWrapper = Wrappers.lambdaQuery(Comment.class)
                .eq(Comment::getIsDelete, 0);
        baseMapper.selectCount(queryWrapper);
        if (baseMapper.selectCount(queryWrapper) > 0) {
            throw new BusinessException("该题目已存在");
        }
        Comment comment = new Comment();
        BeanUtils.copyProperties(requestParam, comment);
        boolean result = this.save(comment);
        ThrowUtils.throwIf(!result, BaseErrorCode.OPERATION_ERROR);
        return comment.getId();
    }


    /**
     * 修改信息
     *
     * @param requestParam 修改请求
     * @return 是否修改成功
     */
    @Override
    @Transactional
    public Boolean updateComment(CommentEditRequestDTO requestParam) {
        if (requestParam == null || requestParam.getId() <= 0) {
            throw new BusinessException(BaseErrorCode.PARAMS_ERROR);
        }
        Comment comment = new Comment();
        BeanUtils.copyProperties(requestParam, comment);
        long id = requestParam.getId();
        // 判断是否存在
        Comment oldComment = this.getById(id);
        ThrowUtils.throwIf(oldComment == null, BaseErrorCode.NOT_FOUND_ERROR);
        boolean result = this.updateById(comment);
        ThrowUtils.throwIf(!result, BaseErrorCode.OPERATION_ERROR);
        return true;
    }

    /**
     * 删除信息
     *
     * @param deleteRequest 删除请求
     * @return 是否修改成功
     */
    @Override
    @Transactional
    public Boolean deleteById(DeleteRequest deleteRequest) {
        if (deleteRequest == null || deleteRequest.getId() <= 0) {
            throw new BusinessException(BaseErrorCode.PARAMS_ERROR);
        }
        long id = deleteRequest.getId();
        // 判断是否存在
        boolean b = this.removeById(id);
        ThrowUtils.throwIf(!b, BaseErrorCode.NOT_FOUND_ERROR);
        return true;
    }


    /**
     * 批量删除
     *
     * @param ids 批量删除的IDS
     * @return 是否删除成功
     */
    @Override
    @Transactional
    public Boolean deleteBatchByIds(Long[] ids) {
        if (ids == null || ids.length == 0) {
            throw new BusinessException(BaseErrorCode.PARAMS_ERROR);
        }
        boolean b = this.removeByIds(Arrays.asList(ids));
        ThrowUtils.throwIf(!b, BaseErrorCode.NOT_FOUND_ERROR);
        return true;
    }
}




